#!/usr/bin/python3
# coding: utf-8
# +-------------------------------------------------------------------
# | 宝塔Linux面板
# +-------------------------------------------------------------------
# | Copyright (c) 2015-2099 宝塔软件(http://bt.cn) All rights reserved.
# +-------------------------------------------------------------------
# | Author: xxx <xxxx@qq.com>
# +-------------------------------------------------------------------

#+--------------------------------------------------------------------
#|   宝塔第三方应用开发DEMO
#+--------------------------------------------------------------------
import sys,os,json

if sys.version[0:1]=='2' :
    import ConfigParser
    
    # 解决ConfigParser小写问题
    class real_conf(ConfigParser.ConfigParser):
        def __init__(self,defaults=None):
            ConfigParser.ConfigParser.__init__(self,defaults=None)
        def optionxform(self, optionstr):
            return optionstr

if sys.version[0:1]=='3' :
    import configparser
    # 解决ConfigParser小写问题
    class real_conf(configparser.ConfigParser):
        def __init__(self,defaults=None):
            configparser.ConfigParser.__init__(self,defaults=None)
        def optionxform(self, optionstr):
            return optionstr
#设置运行目录
os.chdir("/www/server/panel")

#添加包引用位置并引用公共包
sys.path.append("class/")
import public

#from common import dict_obj
#get = dict_obj();


#在非命令行模式下引用面板缓存和session对象
if __name__ != '__main__':
    from BTPanel import cache,session,redirect

    #设置缓存(超时10秒) cache.set('key',value,10)
    #获取缓存 cache.get('key')
    #删除缓存 cache.delete('key')

    #设置session:  session['key'] = value
    #获取session:  value = session['key']
    #删除session:  del(session['key'])



class linksforbt_main:
    __config=""
    __plugin_path = "/www/server/panel/plugin/linksforbt/"
    __run_log=__plugin_path+"log/app.log"
    #构造方法
    def  __init__(self):
        pass

    #自定义访问权限检查
    #一但声明此方法，这意味着可以不登录面板的情况下，直接访问此插件，由_check方法来检测是否有访问权限
    #如果您的插件必需登录后才能访问的话，请不要声明此方法，这可能导致严重的安全漏洞
    #如果权限验证通过，请返回True,否则返回 False 或 public.returnMsg(False,'失败原因')
    #示例未登录面板的情况下访问get_logs方法： /demo/get_logs.json  或 /demo/get_logs.html (使用模板)
    #可通过args.fun获取被请求的方法名称
    #可通过args.client_ip获取客户IP
    #def _check(self,args):
        #token = '123456'
        #limit_addr = ['192.168.1.2','192.168.1.3']
        #if args.token != token: return public.returnMsg(False,'Token验证失败!')
        #if not args.client_ip in limit_addr: return public.returnMsg(False,'IP访问受限!')
        #return redirect('/login')
        #return True
    #添加软连接
    def add_links(self,args):
        if not 'source' in args: args.source = ''
        if not 'target' in args: args.target = ''
        if not 'target_folder' in args: args.target_folder = ''
        
        link_list=self.__get_config('link_list')
        # res_oper=''
        res_oper=public.ExecShell("%soperation.sh link %s %s/%s" % (self.__plugin_path,args.source,args.target,args.target_folder))
        
        #错误代码 1101 源目录不存在 1102 目标目录不为空 1103 目标目录已是软连接 1104 目标目录不是软连接
        if res_oper[0][0:4] == '1101' :
            return {'status':0,'message':'源目录不存在！'}
        if res_oper[0][0:4] == '1102' :
            return {'status':0,'message':'目标目录不为空！'}
        if res_oper[0][0:4] == '1103' :
            return {'status':0,'message':'目标目录已是软连接！'}
        
        link_list.append({'source':args.source,'target_links':args.target+'/'+args.target_folder })
        self.__set_config('link_list',link_list)
        
        return {'status':1,'link_list':link_list,'oper':res_oper[0][0:4]}
    #删除软连接
    def del_links(self,args):
        if not 'target_links' in args: args.target_links = ''
        link_list=self.__get_config('link_list')

        res_oper=public.ExecShell("%soperation.sh unlink %s " % (self.__plugin_path,args.target_links))
        # if res_oper[0][0:4]== '1104' :
        #     return {'status':0,'message':'目标目录不是软连接！'}
        #是软连接删除完清除记录  不是软连接直接清除记录
        
        for i in range(0, len(link_list)): 
            if link_list[i]['target_links'] ==  args.target_links :
                link_list.pop(i)
                break
            pass
        
        self.__set_config('link_list',link_list)
                
        return {'status':1,'link_list':link_list,'oper':res_oper }

    #获取服务状态
    def get_status(self,args):
        link_list=self.__get_config('link_list')
        
        return {'status':1,'link_list':link_list}
        # return {'status': args.status}
    
    #设置服务状态(启动 停止 重启 重载) [目前用不到用了官方的方法]
    def set_status(self,args):
        

        if not 'status' in args: args.status = 0
        args.status = str(args.status)
        public.ExecShell("%soperation.sh service %s" % (self.__plugin_path,args.status))

        return {'status': args.status }
    
    def get_sysset(self,args):
        #生成配置文件副本(正本python2无法操作 很无赖)
        public.ExecShell(self.__plugin_path+"operation.sh cache ")
        #不同版本引用不同类库处理
        config = real_conf()

        # config.readfp(open(self.__config))

        # 读ini文件
        # conf.read(self.__config, encoding="utf-8")  # python3
        
        config.read(self.__config_tmp)  # python2
        sysset={}
        # 获取所有的section
        sections = config.sections()
        for sec in sections:
            item_s={}
            items=config.items(sec)
            for inx,item in enumerate(items):
                item_s.update({item[0]:item[1]})
            sysset.update({sec:item_s})

        # a = config.get("server","LANDING_PAGE")


        return  {'sysset':sysset}
   
    #清理运行日志
    def clear_runlog(self, args):
        public.ExecShell('cat /dev/null > %s' % self.__run_log)
        return public.returnMsg(True, '清理成功')
    #获取面板日志列表
    #传统方式访问get_logs方法：/plugin?action=a&name=demo&s=get_logs
    #使用动态路由模板输出： /demo/get_logs.html
    #使用动态路由输出JSON： /demo/get_logs.json
    def get_logs(self,args):
        filename = self.__run_log
        if os.path.isfile(filename):
            # 宝塔封装的 public.ReadFile 不适合读取大文件
            success, failed = public.ExecShell('tail -n 1000 %s' % filename)
            if success.strip() != '':
                return public.returnMsg(True, success.strip())
            return public.returnMsg(True, '暂无运行日志')

        
    #读取配置项(插件自身的配置文件)
    #@param key 取指定配置项，若不传则取所有配置[可选]
    #@param force 强制从文件重新读取配置项[可选]
    def __get_config(self,key=None,force=False):
        #判断是否从文件读取配置
        if not self.__config or force:
            config_file = self.__plugin_path + 'config.json'
            if not os.path.exists(config_file): return None
            f_body = public.ReadFile(config_file)
            if not f_body: return None
            self.__config = json.loads(f_body)

        #取指定配置项
        if key:
            if key in self.__config: return self.__config[key]
            return None
        return self.__config

    #设置配置项(插件自身的配置文件)
    #@param key 要被修改或添加的配置项[可选]
    #@param value 配置值[可选]
    def __set_config(self,key=None,value=None):
        #是否需要初始化配置项
        if not self.__config: self.__config = {}

        #是否需要设置配置值
        if key:
            self.__config[key] = value

        #写入到配置文件
        config_file = self.__plugin_path + 'config.json'
        public.WriteFile(config_file,json.dumps(self.__config))
        return True

  
